use serde::{Deserialize, Serialize};
use std::fmt::{Display, Formatter};

#[derive(Debug, Clone, Eq, PartialEq, Serialize, Deserialize)]
pub enum ArchType {
    X86,
    X64,
    Arm,
    Arm64,
    Mips,
    Mips64,
    Riscv64,
    LongArch,
    Unknown,
}

impl From<&str> for ArchType {
    fn from(value: &str) -> Self {
        match value {
            "x86" => ArchType::X86,
            "x64" => ArchType::X64,
            "arm" => ArchType::Arm,
            "arm64" => ArchType::Arm64,
            "mips" => ArchType::Mips,
            "mips64" => ArchType::Mips64,
            "riscv64" => ArchType::Riscv64,
            "long_arch" => ArchType::LongArch,
            _ => ArchType::Unknown,
        }
    }
}
impl Display for ArchType {
    fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
        match self {
            ArchType::X86 => write!(f, "x86"),
            ArchType::X64 => write!(f, "x64"),
            ArchType::Arm => write!(f, "arm"),
            ArchType::Arm64 => write!(f, "arm64"),
            ArchType::Mips => write!(f, "mips"),
            ArchType::Mips64 => write!(f, "mips64"),
            ArchType::Riscv64 => write!(f, "riscv64"),
            ArchType::LongArch => write!(f, "long_arch"),
            _ => write!(f, "unknown"),
        }
    }
}

#[derive(Debug, Clone, Eq, PartialEq, Serialize, Deserialize)]
pub enum OsType {
    Windows,
    MacOS,
    Linux,
    FreeBSD,
    OpenBSD,
    DragonFlyBSD,
    Unix,
    Android,
    Ios,
    Unknown,
}

impl Display for OsType {
    fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
        match self {
            OsType::Windows => write!(f, "windows"),
            OsType::MacOS => write!(f, "macos"),
            OsType::Linux => write!(f, "linux"),
            OsType::Unix => write!(f, "unix"),
            OsType::Android => write!(f, "android"),
            OsType::Ios => write!(f, "ios"),
            OsType::Unknown => write!(f, "unknown"),
            OsType::FreeBSD => write!(f, "freebsd"),
            OsType::OpenBSD => write!(f, "openbsd"),
            OsType::DragonFlyBSD => write!(f, "dragonflybsd"),
            #[allow(unreachable_patterns)]
            _ => write!(f, "other"),
        }
    }
}

/// 文件校验方式
#[derive(Debug, Clone, Eq, PartialEq, Serialize, Deserialize)]
pub enum SumType {
    Sha1,
    Sha256,
    Sha512,
    MD5,
}

impl Display for SumType {
    fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
        match self {
            SumType::Sha1 => write!(f, "sha1"),
            SumType::Sha256 => write!(f, "sha256"),
            SumType::Sha512 => write!(f, "sha512"),
            SumType::MD5 => write!(f, "md5"),
        }
    }
}

/// 打包方式
#[derive(Debug, Clone, Eq, PartialEq, Serialize, Deserialize)]
pub enum PackType {
    Zip,
    Tar,
    TarGz,
    TarBz2,
    TarXz,
    Tar7z,
    _7z,
    Executable,
    Dpkg,
    Rpm,
    Unarchived,
}

impl Display for PackType {
    fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
        match self {
            PackType::Zip => write!(f, "zip"),
            PackType::Tar => write!(f, "tar"),
            PackType::TarGz => write!(f, "tar.gz"),
            PackType::TarBz2 => write!(f, "tar.bz2"),
            PackType::TarXz => write!(f, "tar.xz"),
            _ => write!(f, "unknown"),
        }
    }
}
